<template>
    <el-card style="height: 75px;">
        <el-form :inline="true" class="form">
            <el-form-item label="职位搜索">
                <el-input placeholder="请你输入职位关键字" v-model="keyword"></el-input>
            </el-form-item>
            <el-form-item >
                <el-button type="primary" size="default" :disabled="keyword?false:true" @click="search">搜索</el-button>
                <el-button type="primary" size="default" @click="reset">重置</el-button>
            </el-form-item>
        </el-form>
    </el-card>
    <el-card style="margin: 10px 0px;">
        <el-button type="primary" size="default" icon="Plus" @click="addRole" v-has="`btn.Role.add`">添加职位</el-button>
        <el-table border style="margin: 10px 0px;" :data="allRole">
            <el-table-clumn type="index" align="center" label="#"></el-table-clumn>
            <el-table-column label="ID" align="center" prop="id"></el-table-column>
            <el-table-column label="职位名称" align="center" show-overflow-tooltip prop="roleName"></el-table-column>
            <el-table-column label="创建时间" align="center" show-overflow-tooltip prop="createTime"></el-table-column>
            <el-table-column label="更新时间" align="center" show-overflow-tooltip prop="updateTime"></el-table-column>
            <el-table-column label="操作" width="280px" align="center">
                <template #="{row,$index}">
                    <el-button type="primary" size="small" icon="User" @click="setPermission(row)" v-has="`btn.Role.assgin`">分配权限</el-button>
                    <el-button type="primary" size="small" icon="Edit" @click="updateRole(row)" v-has="`btn.Role.update`">编辑</el-button>
                    <el-popconfirm :title="`你确定要删除${row.roleName}吗?`" width="260px" @confirm="removeRole(row.id)">
                        <template #reference>
                            <el-button type="primary" size="small" icon="Delete" v-has="`btn.Role.remove`">删除</el-button>
                        </template>
                    </el-popconfirm>
                </template>
            </el-table-column>
        </el-table>
        <el-pagination
            v-model:current-page="pageNo"
            v-model:page-size="pageSize"
            :page-sizes="[5, 10, 15, 20]"
            :background="true"
            layout="prev, pager, next, jumper,->,total, sizes,"
            :total="total"
            @current-change="getHasRole"
            @size-change="sizeChange"
        />
    </el-card>
    <!-- 添加职位与更新已有职位的对话框 -->
    <el-dialog v-model="dialogVisit" :title="roleParams.id?'更新职位':'添加职位'">
        <el-form :model="roleParams" :rules=rules ref="form">
            <el-form-item label="职位名称"  prop="roleName">
                <el-input placeholder="请你输入职位名称" v-model="roleParams.roleName"></el-input>
            </el-form-item>
        </el-form>
        <template #footer>
            <el-button type="primary" size="default" @click="dialogVisit=false">取消</el-button>
            <el-button type="primary" size="default" @click="save">确定</el-button>
        </template>
    </el-dialog>
    <!-- 抽屉组件，分配职位的菜单权限与按钮权限 -->
    <el-drawer v-model="drawer">
        <template #header>
            <h4>分配菜单与按钮的权限</h4>
        </template>
        <template #default>
            <!-- 树形控件 
                ddefault-expand-all：全部展开
                default-checked-keys：默认勾选的数组
            -->
            <el-tree
                :data="menuArr"
                show-checkbox
                node-key="id"
                default-expand-all
                :default-checked-keys="selectArr"
                :props="defaultProps"
                ref="tree"
            />
        </template>
        <template #footer>
            <div style="flex: auto">
                <el-button @click="drawer=false">取消</el-button>
                <el-button type="primary" @click="handler">确定</el-button>
            </div>
        </template>
    </el-drawer>
</template>

<script lang="ts" setup name="Role">
    import {nextTick,ref,onMounted,reactive} from 'vue'
    import {reqRemoveRole,reqSetPermission,reqAllMenu,reqAddOrUpdateRole,reqAllRoleList} from '@/api/acl/role'
    import type {MenuList,MenuResponseData,RoleData,Records,RoleResponseData} from '@/api/acl/role/type'
    import useLayOutSettingStore from '@/store/modules/setting'
    import { ElMessage } from 'element-plus';

    // 当前页码
    let pageNo=ref<number>(1)
    // 一页展示几条数据
    let pageSize=ref<number>(5)
    // 搜索的关键字
    let keyword=ref<string>('')
    // 存储全部已有的职位
    let allRole=ref<Records>([])
    // 职位的总个数
    let total=ref<number>(0)
    // 获取setting仓库
    let settingStore=useLayOutSettingStore()
    // 控制对话框的隐藏
    let dialogVisit=ref<boolean>(false)
    // 收集新增岗位数据
    let roleParams:RoleData=reactive({
        roleName:''
    })
    // 职位相关的校验规则
    let rules={
        roleName:[
            {required:true,trigger:'blur',validator:validatorRoeName}
        ]
    }
    // 获取表单实例
    let form=ref<any>()
    // 控制抽屉的显示与隐藏
    let drawer=ref<boolean>(false)
    // 定义数组存储用户权限
    let menuArr=ref<MenuList>([])
    // 树形控件的配置选项
    const defaultProps = {
        children: 'children',
        label: 'name',
    }
    // 存储用于勾选的结点的Id(四级)
    let selectArr=ref<number[]>([])
    // 获取tree组件实例
    let tree=ref<any>()


    // 组件挂载完毕
    onMounted(()=>{
        getHasRole()
    })

    // 获取全部现在已有的职位
    async function getHasRole(pager=1){
        // 修改当前的页码
        pageNo.value=pager
        // 发送请求
        let result:RoleResponseData=await reqAllRoleList(pageNo.value,pageSize.value,keyword.value)
        if(result.code==200){
            total.value=result.data.total
            allRole.value=result.data.records
        }
    }

    // 下拉框发生变化的回调
    function sizeChange(){
        getHasRole()
    }

    // 搜索按钮的回调
    function search(){
        // 根据关键字发送请求
        getHasRole()
        // 清空关键字
        keyword.value=''
    }

    // 重置按钮的回调
    function reset(){
        settingStore.refresh=!settingStore.refresh
    }

    // 添加职务按钮的回调
    function addRole(){
        // 对话框显示
        dialogVisit.value=true
        // 清空数据
        Object.assign(roleParams,{
            roleName:'',
            id:0
        })
        // 清空表单校验错误信息
        nextTick(()=>{
            form.value.clearValidate('roleName')
        })
    }

    // 更新已有职位的回调
    function updateRole(row:RoleData){
        // 对话框显示
        dialogVisit.value=true
        // 存储已有的职位
        Object.assign(roleParams,row)
        // 清空表单校验错误信息
        nextTick(()=>{
            form.value.clearValidate('roleName')
        })
    }

    // 自定义校验回调
    function validatorRoeName(rule:any,value:any,callback:any){
        if(value.trim().length>=2){
            callback()
        }else{
            callback(new Error('职位名称至少两位'))
        }
    }

    // 确定按钮的回调
    async function save(){
        // 表单校验结果通过再发请求
        await form.value.validate()
        // 添加|更新职位请求
        let result=await reqAddOrUpdateRole(roleParams)
        if(result.code==200){
            ElMessage({
                type:'success',
                message:roleParams.id?'更新成功':'添加成功'
            })
            // 对话框销售
            dialogVisit.value=false
            // 再次获取全部的已有职位
            getHasRole(roleParams.id?pageNo.value:1)
        }
    }

    // 分配权限按钮的回调
    async function setPermission(row:RoleData){
        // 抽屉显示
        drawer.value=true
        // 收集当前要分配权限的职位的数据
        Object.assign(roleParams,row)
        // 根据职位获取权限的数据
        let result:MenuResponseData=await reqAllMenu((roleParams.id as number))
        if(result.code==200){
            menuArr.value=result.data
            selectArr.value=filterSelectArr(menuArr.value,[])
        }
    }

    // 存储用于勾选的结点的Id
    function filterSelectArr(allData:any,initArr:any){
        allData.forEach((item:any)=>{
            if(item.select&&item.level==4){
                initArr.push(item.id)
            }
            if(item.children&&item.children.length>0){
                filterSelectArr(item.children,initArr)
            }
        })
        return initArr
    }

    // 抽屉确定按钮的回调
    async function handler(){
        // 职位的Id
        const roleId=(roleParams.id as number)
        // 选中结点的Id
        let arr=tree.value.getCheckedKeys()
        // 半选的结点Id
        let arr1=tree.value.getHalfCheckedKeys()
        let permissionId=arr.concat(arr1)
        // 下发权限
        let result:any=await reqSetPermission(roleId,permissionId)
        if(result.code==200){
            // 抽屉关闭
            drawer.value=false
            // 提示信息
            ElMessage({
                type:'success',
                message:'分配权限成功'
            })
            // 页面刷新
            window.location.reload()
        }
    }

    // 删除已有的职位
    async function removeRole(roleId:number){
        let result:any=await reqRemoveRole(roleId)
        if(result.code==200){
            ElMessage({type:'success',message:'删除成功'})
            getHasRole(allRole.value.length>1?pageNo.value:pageNo.value-1)
        }
    }
</script>

<style scoped>
    .form{
        display: flex;
        justify-content: space-between;
        align-items: center;
    }
</style>